package com.awx.client.widget.form;

import java.awt.Dimension;
import java.awt.FlowLayout;

import javax.swing.BorderFactory;
import javax.swing.JButton;
import javax.swing.JComponent;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JSeparator;

public class AwxForm extends JPanel {

	public static final int VERTICAL_ALIGN = 0;
	public static final int HORIZONTAL_ALIGN = 1;

	private static final int ELEMENTS_SPACING = 2;
	private static final int COMPONENT_SPACING = 5;

	private static final int FORM_WIDTH = 500;
	private static final int ELEMENTS_PANEL_WIDTH = FORM_WIDTH - 10;
	private static final Dimension LABEL_DIM = new Dimension( 180, 20 );
	private static final Dimension SEPARATOR_DIM = new Dimension( ELEMENTS_PANEL_WIDTH, 2 );
	private static final Dimension BUTTONS_PANEL_DIM = new Dimension( ELEMENTS_PANEL_WIDTH, 25 );
	private static final int MAX_LABEL_LENGHT = 25;


	private JPanel elementsPanel;
	private JPanel buttonsPanel;
	private AwxDataFormManager manager;
	private Object dataObj;
	private String title;
	private int layoutAligment;
	private JSeparator separator;


	public AwxForm( String title ) {
		this( title, VERTICAL_ALIGN );
	}

	public AwxForm( String title, int layoutAligment ) {
		this.title = title;
		this.layoutAligment = layoutAligment;
		this.visualInit();
	}


	/**
	 * Carga los valores por defecto en el objeto de datos y
	 * luego los muestra en el formulario
	 * @param dataObj
	 * @return el objeto de datos cargado
	 */
	public Object loadDefaultValues() {
		if( this.manager != null ) {
			this.dataObj = this.manager.loadDefaultValues();
			this.manager.loadVisualDefaultForm();
		}
		return this.dataObj;
	}

	/**
	 * Carga solamente el formulario visual, con valores por default
	 * @param dataObj
	 */
	public void loadVisualDefaultValues() {
		if( this.manager != null ) {
			this.manager.loadVisualDefaultForm();
		}
	}

	/**
	 * Carga el formulario con la informacion del objeto de datos
	 * del formulario
	 */
	public void loadForm() {
		if( this.manager != null ) {
			this.manager.loadForm( this.dataObj );
		}
	}

	/**
	 * Carga el objeto de datos con los valores actuales
	 * del formulario
	 * @param dataObj
	 */
	public void loadForm( Object dataObj ) {
		this.setDataObject(dataObj);
		if( this.manager != null ) {
			this.manager.loadForm( this.dataObj );
		}
	}

	/**
	 * Carga el objeto de datos con los valores actuales
	 * del formulario visual
	 * @return el objeto de datos cargado
	 */
	public Object loadDataObject() {
		if( this.manager != null ) {
			this.manager.loadDataObject( this.dataObj );
		}
		return this.dataObj;
	}

	/**
	 * Devuelve el objeto de datos con el cual trabaja el formulario
	 * @return
	 */
	public Object getDataObject() {
		return this.dataObj;
	}

	/**
	 * Carga el objeto de datos con el cual trabaja el formulario
	 * @param dataObj
	 */
	public void setDataObject( Object dataObj ) {
		this.dataObj = dataObj;
	}

	/**
	 * Render the form and let it ready to be added to another panel
	 * @return
	 */
	public JPanel render() {
		//set form size
		Dimension dimension = this.getLayout().minimumLayoutSize( this );
		int formWidth;
		if( dimension.width > FORM_WIDTH ) {
			formWidth = dimension.width;
		} else {
			formWidth = FORM_WIDTH;
		}
		this.setPreferredSize( new Dimension( formWidth , dimension.height ) );

		//set elementsPanel size
		Dimension elementsDim = this.elementsPanel.getLayout().minimumLayoutSize( this.elementsPanel );
		if( elementsDim.width > ELEMENTS_PANEL_WIDTH ) {
			this.elementsPanel.setPreferredSize( elementsDim );
		} else {
			this.elementsPanel.setPreferredSize( new Dimension( ELEMENTS_PANEL_WIDTH, elementsDim.height ) );
		}

		//check separator and buttonsPanel
		if( this.buttonsPanel.getComponentCount() > 0 ) {
			this.separator.setPreferredSize( SEPARATOR_DIM );
			this.buttonsPanel.setPreferredSize( BUTTONS_PANEL_DIM );
		}
		return this;
	}

	private void visualInit() {
		//main panel
		this.setLayout( new VerticalLayout(2) );
		this.setBorder( BorderFactory.createTitledBorder( this.title) );

		//elements panel
		this.elementsPanel = new JPanel();
		if( layoutAligment == HORIZONTAL_ALIGN ) {
			this.elementsPanel.setLayout( new FlowLayout( FlowLayout.CENTER, ELEMENTS_SPACING, 0 ) );

		} else {
			this.elementsPanel.setLayout( new VerticalLayout( ELEMENTS_SPACING, VerticalLayout.LEFT ) );
		}
		this.add( this.elementsPanel );

		//separator
		this.separator = new JSeparator();
		this.add( separator );

		//buttons panel
		this.buttonsPanel = new JPanel( new FlowLayout( FlowLayout.RIGHT, ELEMENTS_SPACING, 0 ) );
		this.add( this.buttonsPanel );
	}


	public void addElement( String text, JComponent component ) {
		JPanel horPanel = new JPanel( new FlowLayout( FlowLayout.CENTER, COMPONENT_SPACING, 0 ) );
		JLabel label = new JLabel( text );
		if( text.length() > MAX_LABEL_LENGHT ) {
			label.setPreferredSize( new Dimension( LABEL_DIM.width, LABEL_DIM.height *
					( (text.length() / MAX_LABEL_LENGHT) + 1 )  ) );
		} else {
			label.setPreferredSize( LABEL_DIM );
		}
		label.setHorizontalAlignment( JLabel.RIGHT );
		horPanel.add( label );
		horPanel.add( component );
		this.elementsPanel.add( horPanel );
	}

	public void addButton( JButton button ) {
		this.buttonsPanel.add( button );
	}


	public void setDataFormManager(AwxDataFormManager manager) {
		this.manager = manager;
	}

}










